package com.cyanite.playlv2;

import com.cyanite.playlv2.app.LoadableListActivityWithViewAndHeader;
import com.cyanite.playlv2.util.MenuUtils;
import com.cyanite.playlv2.util.NotificationsUtil;
import com.cyanite.playlv2.util.UiUtil;
import com.cyanite.playlv2.widget.SegmentedButton;
import com.cyanite.playlv2.widget.ShareTripListAdapter;
import com.cyanite.playlv2.widget.SegmentedButton.OnClickListenerSegmentedButton;
import com.cyanite.playlv2api.types.Trip;
import com.cyanite.playlv2api.types.Group;
import com.cyanite.playlv2.R;

import android.app.AlertDialog;
import android.app.Dialog;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.AsyncTask;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ScrollView;

public class ShareActivity extends LoadableListActivityWithViewAndHeader {

    private static final int MENU_GROUP_SEARCH = 0;
    private static final int MENU_REFRESH = 1;
    private static final int MENU_SEARCH = 2;
    private static final int MENU_CREATE_TRIP = 3;

    private StateHolder mStateHolder;
    private ViewGroup mLayoutEmpty;

    private BroadcastReceiver mLoggedOutReceiver = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            finish();
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        registerReceiver(mLoggedOutReceiver, new IntentFilter(PlayLv2.INTENT_ACTION_LOGGED_OUT));

    	mStateHolder = new StateHolder();
    	mStateHolder.setUserId(((PlayLv2) getApplication()).getUserId());
        ensureUi();
        mStateHolder.startShareHistoryTask(this);
    }

    private void ensureUi() {
        setRefreshProgressBarEnable(false);
        SegmentedButton buttons = getHeaderButton();
        buttons.clearButtons();
        buttons.addButtons(
            getString(R.string.share_activity_btn_ongoing),
            getString(R.string.share_activity_btn_upcoming));
        buttons.setFocusable(false);

        buttons.setOnClickListener(new OnClickListenerSegmentedButton() {
            public void onClick(int index) {
                if (index == 0) {
                    mStateHolder.setIsPageOngoing(true);
                }   else {
                    mStateHolder.setIsPageOngoing(false);
                }
                updateUi();
            }
        });

        ImageView btnRefresh = getRightButton();
        btnRefresh.setBackgroundResource(R.drawable.refresh_button);
        btnRefresh.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (!mStateHolder.getIsRunningTask()) {
                    mStateHolder.startShareHistoryTask(ShareActivity.this);
                }
                setRefreshProgressBarEnable(true);
                getRightButton().setBackgroundResource(R.drawable.refresh_button_normal);
            }
        });
        ImageView btnNewTrip = getLeftButton();
        btnNewTrip.setBackgroundResource(R.drawable.new_trip_button);
        btnNewTrip.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                startActivity(new Intent(ShareActivity.this, TripCreateMainActivity.class));
            }
        });
        LayoutInflater inflater = LayoutInflater.from(this);
        if (UiUtil.sdkVersion() > 3) {
            mLayoutEmpty = (ScrollView)inflater.inflate(
                    R.layout.trips_activity_empty, null);

            Button btnAddTrips = (Button)mLayoutEmpty.findViewById(
                    R.id.tripsActivityEmptyBtnAddTrips);
            btnAddTrips.setOnClickListener(new OnClickListener() {
                @Override
                public void onClick(View v) {
                    startActivity(new Intent(ShareActivity.this, TripCreateMainActivity.class));
                }
            });
        } else {
            mLayoutEmpty = (ScrollView)inflater.inflate(
                    R.layout.trips_activity_empty_sdk3, null);
        }

        mLayoutEmpty.setLayoutParams(new LinearLayout.LayoutParams(
                LinearLayout.LayoutParams.FILL_PARENT, LinearLayout.LayoutParams.FILL_PARENT));
    }

    private void updateUi() {
        Group<Trip> trips = null;
        if (mStateHolder.getIsPageOngoing())    {
            trips = mStateHolder.getTripsOngoing();
        }   else {
            trips = mStateHolder.getTripsUpcoming();
        }
        if (trips != null && trips.size() > 0)  {
            ShareTripListAdapter adapter = new ShareTripListAdapter(this,
                    ((PlayLv2) getApplication()).getRemoteResourceManager(), btnOnClickListener);
            adapter.setGroup(trips);
            getListView().setAdapter(adapter);
            getListView().setDividerHeight(0);
        }   else {
            getListView().setAdapter(null);
            setEmptyView(mLayoutEmpty);
        }

        if (mStateHolder.getIsRunningTask()) {
            setProgressBarIndeterminateVisibility(true);
            setLoadingView();
        }else {
            setProgressBarIndeterminateVisibility(false);
        }
    }

    @Override
    public void onResume() {
        super.onResume();
    }

    @Override
    public void onPause() {
        super.onPause();

        if (isFinishing()) {
            unregisterReceiver(mLoggedOutReceiver);
            mStateHolder.cancel();
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        super.onCreateOptionsMenu(menu);
        menu.add(MENU_GROUP_SEARCH, MENU_REFRESH, Menu.NONE, R.string.refresh)
                .setIcon(R.drawable.ic_menu_refresh);
        menu.add(MENU_GROUP_SEARCH, MENU_SEARCH, Menu.NONE, R.string.search_label)
        .setIcon(R.drawable.ic_menu_search);
        menu.add(Menu.NONE, MENU_CREATE_TRIP, Menu.NONE, R.string.preferences_trip_add_title)
                .setIcon(R.drawable.ic_menu_create_trip);
        MenuUtils.addPreferencesToMenu(this, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case MENU_REFRESH:
                if (!mStateHolder.getIsRunningTask())
                mStateHolder.startShareHistoryTask(this);
                return true;
            case MENU_SEARCH:
                return  true;
            case MENU_CREATE_TRIP:
                startActivity(new Intent(ShareActivity.this, TripCreateMainActivity.class));
                return true;
            default:
                break;
        }
        return super.onOptionsItemSelected(item);
    }

    @Override
    public int getNoSearchResultsStringId() {
        return R.string.no_trip_created;
    }

    @Override
    public boolean onKeyDown(int keyCode, KeyEvent event) {
        if (keyCode == KeyEvent.KEYCODE_BACK) {
            Dialog dialog = new AlertDialog.Builder(this)
            .setTitle(this.getResources().getString(R.string.app_name))
            .setMessage(this.getResources().getString(R.string.exit_note))
            .setPositiveButton(this.getResources().getString(R.string.ok), new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int whichButton) {
                    finish();
                    android.os.Process.killProcess(android.os.Process.myPid());
                }
            })
            .setNegativeButton(this.getResources().getString(R.string.cancel), new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int whichButton) {
                }
            }).create();
            dialog.show();
            return true;
        }
        else
            return super.onKeyDown(keyCode, event);
    }

    private ShareTripListAdapter.ButtonRowClickHandler btnOnClickListener = new ShareTripListAdapter.ButtonRowClickHandler(){
        public void onButtonClick(Trip trip) {
            Intent intent = new Intent(ShareActivity.this, TaskCategoryActivity.class);
            intent.putExtra(TaskCategoryActivity.EXTRA_TRIP_PARCEL, trip);
            startActivity(intent);
        }

        @Override
        public void onBtnClickInfo(Trip trip) {
            trip.setUserId(mStateHolder.getUserId());
            Intent intent = new Intent(ShareActivity.this, TripDetailsActivity.class);
            intent.putExtra(TripDetailsActivity.EXTRA_TRIP_PARCEL, trip);
            startActivity(intent);
        }
    };

    private void onTaskStart() {
        setProgressBarIndeterminateVisibility(true);
        setLoadingView();
    }

    private void onTaskComplete(Group<Trip> trips, Exception ex) {

        getRightButton().setBackgroundResource(R.drawable.refresh_button);
        setRefreshProgressBarEnable(false);
        mStateHolder.setIsRunningTask(false);
        setProgressBarIndeterminateVisibility(false);
        mStateHolder.getTripsOngoing().clear();
        mStateHolder.getTripsUpcoming().clear();
        if (trips != null && trips.size() > 0) {
            for (Trip it : trips) {
                if (it.getProcess() < 0) {
                    mStateHolder.getTripsUpcoming().add(it);
                }
                else {
                    mStateHolder.getTripsOngoing().add(it);
                }
            }
        } else if (ex != null) {
            NotificationsUtil.ToastReasonForFailure(this, ex);
        }

        updateUi();
    }

    private static class TaskTrips extends AsyncTask<Void, Void, Group<Trip>> {

    	private PlayLv2 mPlayLv2;
    	private ShareActivity mActivity;
        private Exception mException;
        private String mViewUserId;

        public TaskTrips(ShareActivity activity, String viewUserId) {
            mPlayLv2 = ((PlayLv2) activity.getApplication());
        	mActivity = activity;
        	mViewUserId = viewUserId;
        }

        @Override
        public Group<Trip> doInBackground(Void... params) {
        	try {
        	    return mPlayLv2.getPlayLv2Api().trips(mViewUserId, "1");
            } catch (Exception ex) {
            	mException = ex;
            	return null;
            }
        }

        @Override
        protected void onPreExecute() {
            mActivity.onTaskStart();
        }

        @Override
        public void onPostExecute(Group<Trip> trips) {
        	if (mActivity != null) {
        		mActivity.onTaskComplete(trips, mException);
        	}
        }
    }

    private static class StateHolder {
        private Group<Trip> mTripsOngoing;
        private Group<Trip> mTripsUpcoming;
        private boolean mIsRunningTask;
        private TaskTrips mTaskTrips;
        private boolean mPageIsOngoing;
        private String mUserId;

        public StateHolder() {
        	mIsRunningTask = false;
        	mTripsOngoing = new Group<Trip>();
        	mTripsUpcoming = new Group<Trip>();
        	mPageIsOngoing = true;
        }

        public String getUserId()    {
            return mUserId;
        }

        public void setUserId(String userId)    {
            mUserId = userId;
        }

        public Group<Trip> getTripsOngoing() {
            return mTripsOngoing;
        }

        public Group<Trip> getTripsUpcoming() {
            return mTripsUpcoming;
        }

        public boolean getIsRunningTask() {
        	return mIsRunningTask;
        }

        public void setIsRunningTask(boolean isRunning) {
        	mIsRunningTask = isRunning;
        }

        public boolean getIsPageOngoing() {
            return mPageIsOngoing;
        }

        public void setIsPageOngoing(boolean isOngoing) {
            mPageIsOngoing = isOngoing;
        }

        public void startShareHistoryTask(ShareActivity activity) {
        	if (!mIsRunningTask) {
        	    mTaskTrips = new TaskTrips(activity, mUserId);
        	    mTaskTrips.execute();
        		mIsRunningTask = true;
        	}
        }

        public void cancel() {
        	if (mIsRunningTask) {
        		mTaskTrips.cancel(true);
        		mIsRunningTask = false;
        	}
        }
    }
}
